<template>
  <div>
    <el-dialog
      v-model="dialogVisible"
      width="80%"
      align-center
      :show-close="false"
      @open="handleOpen"
      @close="handleClose"
      draggable
    >
      <template #header="{ close }">
        <div class="dialog-header flex justify-between items-center">
          <div>{{ title }}</div>
          <el-icon class="el-icon--left cursor-pointer" @click="close"
            ><CircleCloseFilled color="#fff"
          /></el-icon>
        </div>
      </template>
      <!-- 基本信息 -->
      <div class="bg-white mt-[10px]">
        <BaseHead>基本信息</BaseHead>
        <div class="p-[10px]">
          <el-form :model="editForm" :rules="rules" label-width="130px" ref="editFormRef">
            <el-row :gutter="20">
              <el-col :span="12">
                <el-form-item label="科研标准名称" prop="name">
                  <el-input
                    placeholder="请输入科研标准名称"
                    clearable
                    v-model="editForm.name"
                  ></el-input>
                </el-form-item>
              </el-col>
              <el-col :span="12">
                <el-form-item prop="prefix" label="科目编号前缀">
                  {{ editForm.prefix }}
                </el-form-item>
              </el-col>
              <el-col :span="12">
                <el-form-item label="经费管理政策文件" prop="policyFileId">
                  <FileUpload :uploadUrl="uploadUrl" v-model="fileList" @change="fileChange" />
                </el-form-item>
              </el-col>
              <el-col :span="12">
                <el-form-item label="是否实行间接费" prop="executeIndirectFee">
                  <el-select v-model="editForm.executeIndirectFee" placeholder="是否实行间接费">
                    <el-option label="是" value="1" />
                    <el-option label="否" value="0" /> </el-select
                ></el-form-item>
              </el-col>
            </el-row>
          </el-form>
        </div>
      </div>
      <!-- 预算科目 -->
      <div class="bg-white mt-[10px]">
        <BaseHead style="border-bottom: 0">
          预算科目 <el-button @click="handeAdd">添加</el-button></BaseHead
        >
        <el-table
          :data="subjectList"
          class="w-full"
          border
          row-key="code"
          default-expand-all
          :tree-props="{ hasChildren: 'hasChild' }"
          stripe
        >
          <el-table-column label="预算科目编号" prop="code" />
          <el-table-column label="预算科目名称">
            <template #default="{ row }">
              <div class="flex items-center">
                <span class="no-empty-icon">*</span>
                <el-input clearable v-model="row.name"></el-input>
              </div>
            </template>
          </el-table-column>
          <el-table-column label="经费调整限制" width="200px">
            <template #default="{ row }">
              <CommonSelect
                :isFetch="false"
                :dataList="feeList.value"
                v-model="row.feeLimit"
                valueKey="code"
              />
            </template>
          </el-table-column>
          <el-table-column label="预算填写说明">
            <template #default="{ row }">
              <el-input clearable type="textarea" v-model="row.note"></el-input>
            </template>
          </el-table-column>
          <el-table-column fixed="right" label="操作" width="180" align="center">
            <template #default="{ row }">
              <el-button type="primary" size="small" plain @click="handleDel(row)" >
                删除
              </el-button>
              <el-button type="primary" size="small" plain @click="handeAddChild(row)">
                添加子科目
              </el-button>
            </template>
          </el-table-column>
        </el-table>
      </div>
      <template #footer>
        <div class="dialog-footer">
          <div class="operate-btns">
            <el-button type="primary" @click="save">保存</el-button>
            <el-button type="primary" @click="dialogVisible = false">关闭</el-button>
          </div>
        </div>
      </template>
    </el-dialog>
  </div>
</template>

<script setup>
import BaseHead from "@/views/project/components/BaseHead.vue";
import CommonSelect from "@/views/project/components/CommonSelect.vue";
import { addRecords, editRecords, recordsDetail, getPrefix } from "@/api/project/zx/ysbzsz";
import FileUpload from "@/views/project/components/FileUpload.vue";
import { ElMessage } from "element-plus";
import { assignObj } from "@/utils/main";
import useCommonFetch from "@/hooks/useCommonFetch";
const projectClass = inject("projectClass");
const feeList = ref([]); //经费调整限制下拉列表
const dialogVisible = ref(false);
const editFormRef = ref();
const detailData = ref(null);
const fileList = ref([]);
const subjectList = ref([]);
const operateId = ref(null);
const title = computed(() => {
  return operateId.value ? "预算标准编辑" : "预算标准新增";
});
const uploadUrl = `/commonFile/uploadFile?modelName=评审方案设置`;
//基本信息表单
const editForm = reactive({
  name: "",
  prefix: "",
  policyFileId: "",
  executeIndirectFee: "",
});
const rules = reactive({
  name: [
    {
      required: true,
      message: "科研标准名称必填",
    },
  ],
});
//获取数据详情
const getDetail = async () => {
  try {
    const res = await recordsDetail(operateId.value);
    detailData.value = res.data;
    fileList.value = res.data.policyFileList || [];
  } catch (error) {
    console.log(error);
  }
};
// 新增
const add = async () => {
  operateId.value = null;
  dialogVisible.value = true;
  await getMaxPrefix();
  //默认生成一行预算科目数据
  subjectList.value = [getSubjectItem(editForm.prefix, 0)];
};
// 编辑
const edit = async (id) => {
  operateId.value = id;
  dialogVisible.value = true;
  await getDetail();
  nextTick(() => {
    //表单表格赋值
    assignObj(editForm, detailData.value);
    subjectList.value = detailData.value.subjectList;
    if (!subjectList.value.length) {
      //编辑的时候如果subjectList字段为空 也默认生成一行预算科目数据
      subjectList.value = [getSubjectItem(editForm.prefix, 0)];
    }
  });
};
defineExpose({ add, edit });
const emit = defineEmits(["save-success"]);
//点击保存
const save = () => {
  try {
    editFormRef.value?.validate(async (valid) => {
      if (valid) {
        let validateFlag = true;
        let nameArray = [];
        const validateFiled = (rows) => {
          for (let i = 0; i < rows.length; i++) {
            if (rows[i].name == "") {
              validateFlag = false;
            }
            nameArray.push(rows[i].name);
            validateFiled(rows[i].children);
          }
        };
        validateFiled(subjectList.value);
        //验证预算科目表格数据中的预算科目名称是否都已填写
        if (!validateFlag) {
          ElMessage({
            message: "请检查预算科目名称是否全部填写！",
            type: "error",
          });
          return;
        }
        //验证预算科目名称是否重复
        const nameSets = new Set(nameArray);
        if (nameSets.size < nameArray.length) {
          ElMessage({
            message: "预算科目名称不允许重复！",
            type: "error",
          });
          return;
        }
        let res;
        let params = {
          standard: {
            projectClass,
            ...editForm,
          },
          subjectList: subjectList.value,
        };
        if (operateId.value) {
          params.standard.id = operateId.value;
          res = await editRecords(params);
        } else {
          res = await addRecords(params);
        }
        if (res.code === 200) {
          ElMessage({
            message: "操作成功！",
            type: "success",
          });
          dialogVisible.value = false;
          emit("save-success");
        }
      }
    });
  } catch (error) {
    console.log(error);
  }
};
//点击添加科目
const handeAdd = () => {
  subjectList.value.push(getSubjectItem(editForm.prefix, subjectList.value.length));
};
//点击添加子科目
const handeAddChild = (row) => {
  row.children.push(getSubjectItem(row.code, row.children.length));
};
//点击删除一行
const handleDel = (row) => {
  const deleteRow = (rows) => {
    for (let i = 0; i < rows.length; i++) {
      if (rows[i].code === row.code) {
        // 找到要删除的行，直接删除
        rows.splice(i, 1);
        break;
      } else if (rows[i].children) {
        // 如果存在子项，递归搜索子项
        deleteRow(rows[i].children);
      }
    }
  };
  // 在顶层数据上调用函数，因为顶层数据可能直接包含要删除的项或其子项引用相同的项
  deleteRow(subjectList.value);
  //更新节点数据code
  setCodeToTree(subjectList.value, editForm.prefix);
};
//获取最大预算科目前缀
const getMaxPrefix = async () => {
  try {
    const params = {
      projectClass,
    };
    const res = await getPrefix(params);
    const maxPrefix = res.data;
    //如果maxPrefix为空 生成初始编号0001
    if (!maxPrefix) {
      const charCode = projectClass == "zXProject" ? "Z" : projectClass == "yfContract" ? "H" : "X";
      editForm.prefix = charCode + "0001";
    } else {
      editForm.prefix = getCurrentPrefix(maxPrefix);
    }
  } catch (error) {
    console.log(error);
  }
};
//获取当前prefix的值 最大预算科目前缀加1
const getCurrentPrefix = (maxPrefix) => {
  const code = maxPrefix.slice(0, 1);
  const number = maxPrefix.slice(1);
  const num = parseInt(number) + 1; //去掉前导0 加1 生成新编号数值
  const newNumber = num.toString().padStart(4, "0"); //补全4位字符串
  return code + newNumber;
};
//根据父节点编号生成子节点编号
const getChildNum = (prefix, index) => {
  const currentIndex = index + 1;
  const currentIndexStr = currentIndex.toString().padStart(2, "0"); //补全2位字符串
  return prefix + currentIndexStr;
};
//生成一个新的预算科目对象（预算科目表格的一行数据）
function getSubjectItem(prefix, index) {
  const baseSubject = {
    code: getChildNum(prefix, index),
    name: "",
    feeLimit: "", //经费调整限制
    note: "",
    children: [],
  };
  return baseSubject;
}
//更新预算科目树的code
function setCodeToTree(tree, parentCode = "") {
  tree.forEach((node, index) => {
    const currentNodeIndex = index + 1;
    const currentNodeCode = `${parentCode}${currentNodeIndex.toString().padStart(2, "0")}`;
    // 给当前节点添加code字段
    node.code = currentNodeCode;
    // 如果有子节点，则递归处理子节点
    if (node.children && node.children.length > 0) {
      setCodeToTree(node.children, currentNodeCode);
    }
  });
}
//打开弹窗
const handleOpen = async () => {
  feeList.value = useCommonFetch("经费调整限制");
};
//关闭弹窗
const handleClose = () => {
  //重置基本信息表单数据和科目预算数据
  editFormRef.value.resetFields();
  subjectList.value = [];
  fileList.value = [];
};
//上传的文件改变
const fileChange = () => {
  const ids = fileList.value.map((item) => {
    const id = item.response ? item.response.data : item.id;
    return id;
  });
  editForm.policyFileId = ids.join(",");
};
</script>

<style scoped lang="scss">
@import url("@/views/project/index.scss");
</style>
